using System;
//using Linq;
using System.Configuration;
using System.Data;
using System.Data.Common;
//using Linq;
using System.Windows.Forms;
//using clsVariables;
using Microsoft.VisualBasic;



#region  NOTAS
//SC: Si uso esto condiciono a que siempre sea el mismo factory para TODO
//#Region "                                                               FactoryBBDD"
//   Private p_FactoryBBDD As DbProviderFactory
//   Public Property FactoryBBDD() As DbProviderFactory
//      Get
//         Return p_FactoryBBDD
//      End Get
//      Set(ByVal value As DbProviderFactory)
//         p_FactoryBBDD = value
//      End Set
//   End Property
//#End Region
//'
#endregion
//'
#region  Imports
#endregion
//'
/// <summary>
/// Contiene las acciones con datos genéricas usando Factory y los tratamientos específicos de datos según provider (como la fecha en Mysql).
/// </summary>
/// <remarks></remarks>
public class clsBBDD
{

    //'
    #region  Variables
    public static DbProviderFactory FactoryBBDD = null;
    #endregion
    //'
    #region  Tratamiento datos según provider
    //'
    /// <summary>
    /// Dependiendo de la BBDD los datos se comportan distinto (por ejemplo las fechas en MySQl). Esta función adpata el dato a lo esperado
    /// Ej en MySQl: Le pasas date y devuelve mysqldate. LE pasas mysqldate y devuelve date
    /// </summary>
    /// <param name="ovalue"></param>
    /// <returns></returns>
    /// <remarks></remarks>
    public static object TratamientoValorSegunProvider(object ovalue)
    {
        //CallByName(Me, "TratamientoRowSegunProvider_" & str_ProviderNombreAplicacion, CallType.Method, _
        //                              Dr, strNombreControlSinPrefijo, ovalue)
        switch (clsVariables.e_ProviderNombreAplicacion)
        {
            case clsVariables.eProviderNombre.MySqlClient:

                return TratamientoValorSegunProvider_MySqlClient(ovalue);
            default:
                Utiles.Errores.LanzarError(null, "TratamientoValorSegunProvider", "Provider no programado: " + clsVariables.e_ProviderNombreAplicacion, null, MessageBoxIcon.Information, true);
                return ovalue;
        }
    }
    //'
    private static object TratamientoValorSegunProvider_MySqlClient(object objValue)
    {
        MySql.Data.Types.MySqlDateTime dMySql;
        DateTime D;
        //'
        if (objValue is DateTime)
        {
            D = Convert.ToDateTime(objValue);
            //Dim d2 As Object = DbType.Date
            //d2 = objValue
            return new MySql.Data.Types.MySqlDateTime(D);
            //
        }
        else if (objValue is MySql.Data.Types.MySqlDateTime)
        {
            dMySql = (MySql.Data.Types.MySqlDateTime)objValue;
            return new DateTime(dMySql.Year, dMySql.Month, dMySql.Day, dMySql.Hour, dMySql.Minute, dMySql.Second);
            //
        }
        else
        {
            return objValue;
        }
    }
    //'
    #endregion
    //'
    /// <summary>
    /// Devuelve un objeto System.Data.DataTable que contiene información sobre todos los proveedores instalados que implementan DbProviderFactoryBBDD.
    /// </summary>
    /// <returns>System.Data.DataTable con los objetos System.Data.DataRow que contienen los datos siguientes:
    /// Ordinal de la columna Nombre de la columna.  Descripción
    /// 0 Name Nombre legible para el proveedor de datos.
    /// 1 Description Descripción legible del proveedor de datos.
    /// 2 InvariantName Nombre que se puede utilizar para hacer referencia al proveedor de datos mediante programación.
    /// 3 AssemblyQualifiedName Nombre completo de la clase Factory, que contiene información suficiente para crear instancias del objeto.
    /// </returns>
    /// <remarks></remarks>
    public static System.Data.DataTable DtObtenerGetFactoryClasses()
    {
        return System.Data.Common.DbProviderFactories.GetFactoryClasses();
    }
    //'
    /// <summary>
    /// Obtiene el nombre del factory de una cadena de conexión y lo guarda en un Enum
    /// </summary>
    /// <param name="origen"></param>
    /// <returns></returns>
    /// <remarks></remarks>
    public static clsVariables.eProviderNombre ObtenerFactoryDDBB(clsVariables.e_TipoOrigen origen)
    {
        clsVariables.eProviderNombre ret = clsVariables.eProviderNombre.Ninguno;
        ConnectionStringSettings c = clsVariables.e_Cc(origen);
        switch (c.ProviderName)
        {
            case "System.Data.Odbc":

                ret = clsVariables.eProviderNombre.Odbc;
                break;
            case "System.Data.OleDb":

                ret = clsVariables.eProviderNombre.OleDb;
                break;
            case "System.Data.OracleClient":

                ret = clsVariables.eProviderNombre.OracleClient;
                break;
            case "System.Data.SqlClient":

                ret = clsVariables.eProviderNombre.SqlClient;
                break;
            case "Microsoft.SqlServerCe.Client":

                ret = clsVariables.eProviderNombre.SqlServerCe;
                break;
            case "System.Data.SqlServerCe.3.5":

                ret = clsVariables.eProviderNombre.SqlServerCe35;
                break;
            case "Oracle.DataAccess.Client":

                ret = clsVariables.eProviderNombre.OracleDataAccessClient;
                break;
            case "MySql.Data.MySqlClient":

                ret = clsVariables.eProviderNombre.MySqlClient;
                break;
        }
        return ret;
    }
    //'
    #region  Acciones Datos
    //'
    /// <summary>
    /// Le pasas un valor y si es 1 devuelve True si es diferente devuelve False. Esto es pq. las columnas tipo boolean en cada BBDD se comporta distinto
    /// Normalmente solo necesario para DataroWs
    /// </summary>
    /// <returns></returns>
    /// <remarks></remarks>
    public static bool DevolverBooleano(object Valor)
    {
        if (Information.IsNumeric(Valor.ToString()) && System.Convert.ToInt32(Valor) == 1)
        {
            return true;
        }
        else
        {
            return false;
        }
    }
    //'
    #region  ObtenerSchemaTable
    public static DataTable ObtenerSchemaTable(string selectCommandText, clsVariables.e_TipoOrigen origen)
    {
        DataTable ret = new DataTable();
        try
        {
            ConnectionStringSettings c = clsVariables.e_Cc(origen);
            FactoryBBDD = DbProviderFactories.GetFactory(c.ProviderName);
            using (DbConnection cn = FactoryBBDD.CreateConnection())
            {
                cn.ConnectionString = c.ConnectionString;
                cn.Open();
                using (DbCommand cm = FactoryBBDD.CreateCommand())
                {
                    cm.Connection = cn;
                    cm.CommandType = CommandType.Text;
                    cm.CommandText = selectCommandText;

                    IDataReader r = cm.ExecuteReader(CommandBehavior.CloseConnection);
                    ret = r.GetSchemaTable();
                    //' Create the DbDataAdapter.
                    //Dim adapter As DbDataAdapter = FactoryBBDD.CreateDataAdapter()
                    //adapter.SelectCommand = cm
                    //'Dim table As New DataTable : adapter.Fill(table) ' Fill the DataTable
                    //adapter.Fill(ret)
                }

            }

        }
        catch (Exception ex)
        {
            throw (ex);
        }
        return ret;
    }
    //'
    public static DataTable ObtenerSchema(string selectCommandText, clsVariables.e_TipoOrigen origen)
    {
        DataTable ret = new DataTable();
        try
        {
            ConnectionStringSettings c = clsVariables.e_Cc(origen);
            FactoryBBDD = DbProviderFactories.GetFactory(c.ProviderName);
            using (DbConnection cn = FactoryBBDD.CreateConnection())
            {
                cn.ConnectionString = c.ConnectionString;
                cn.Open();
                if (string.IsNullOrEmpty(selectCommandText))
                {
                    ret = cn.GetSchema();
                }
                else
                {
                    ret = cn.GetSchema(selectCommandText);
                }
                cn.Close();
            }

        }
        catch (Exception ex)
        {
            throw (ex);
        }
        return ret;
    }
    #endregion
    //'
    /// <summary>
    /// Ejecutar un stored procedure
    /// </summary>
    /// <returns>retorna el parametro @Ret</returns>
    /// <remarks></remarks>
    public static int EjecutarProcedure(string selectCommandText, clsVariables.e_TipoOrigen origen) // ByVal selectCommandText As String, ByVal origen As e_TipoOrigen) As Integer
    {
        int ret = -1;
        Exception ex = null;
        try
        {
            ConnectionStringSettings c = clsVariables.e_Cc(origen);
            FactoryBBDD = DbProviderFactories.GetFactory(c.ProviderName);
            using (DbConnection cn = FactoryBBDD.CreateConnection())
            {
                cn.ConnectionString = c.ConnectionString;
                cn.Open();
                using (DbCommand cm = FactoryBBDD.CreateCommand())
                {
                    cm.Connection = cn;
                    DbParameter p = FactoryBBDD.CreateParameter();
                    p.ParameterName = "@Ret";
                    p.DbType = System.Data.DbType.Int32;
                    p.Direction = ParameterDirection.InputOutput;
                    p.Value = DBNull.Value;
                    cm.Parameters.Add(p);
                    cm.CommandType = CommandType.StoredProcedure;
                    cm.CommandText = selectCommandText;
                    try
                    {
                        //ret = cm.ExecuteNonQuery()
                        cm.ExecuteNonQuery();
                        ret = (int)cm.Parameters["@Ret"].Value;
                    }
                    catch (Exception exCommand)
                    {

                        ex = exCommand;
                    }
                }

            }

        }
        catch (Exception exConnect)
        {

            ex = exConnect;
        }
        if (ret != 1000)
        {
            Utiles.Errores.LogGrabar("agnProcedureExecute", ex, "", "");
        }
        return ret;
    }
    //
    /// <summary>
    /// Devuelve la primera columna de la primera fila de un sql en tipo INTEGER (util para max,sum,...)
    /// NO OBTIENE STRINGS! Alternativamente usar ObtenerDouble y ObtenerString
    /// </summary>
    /// <param name="selectCommandText"></param>
    /// <param name="origen"></param>
    /// <returns></returns>
    /// <remarks></remarks>
    public static int EjecutarExecuteScalar(string selectCommandText, clsVariables.e_TipoOrigen origen)
    {
        int ret = -1;
        try
        {
            ConnectionStringSettings c = clsVariables.e_Cc(origen);
            FactoryBBDD = DbProviderFactories.GetFactory(c.ProviderName);
            using (DbConnection cn = FactoryBBDD.CreateConnection())
            {
                cn.ConnectionString = c.ConnectionString;
                cn.Open();
                using (DbCommand cm = FactoryBBDD.CreateCommand())
                {
                    cm.Connection = cn;
                    cm.CommandType = CommandType.Text;
                    cm.CommandText = selectCommandText;
                    ret = (int)cm.ExecuteScalar();
                }
            }
        }
        catch (Exception ex)
        { throw (ex); }
        return ret;
    }
    //'
    /// <summary>
    /// Ejecutar un SQL directo.
    /// </summary>
    /// <param name="selectCommandText"></param>
    /// <param name="origen"></param>
    /// <returns></returns>
    /// <remarks></remarks>
    public static int EjecutarExecuteNonQuery(string selectCommandText, clsVariables.e_TipoOrigen origen)
    {
        int ret = -1;
        try
        {
            ConnectionStringSettings c = clsVariables.e_Cc(origen);
            FactoryBBDD = DbProviderFactories.GetFactory(c.ProviderName);
            using (DbConnection cn = FactoryBBDD.CreateConnection())
            {
                cn.ConnectionString = c.ConnectionString;
                cn.Open();
                using (DbCommand cm = FactoryBBDD.CreateCommand())
                {
                    cm.Connection = cn;
                    cm.CommandType = CommandType.Text;
                    cm.CommandText = selectCommandText;
                    ret = cm.ExecuteNonQuery();
                }
            }

            //
            return ret;
        }
        catch (Exception ex)
        {
            throw (ex);
            //return ret;
        }
    }
    //'
    //'
    /// <summary>
    /// Actualizar datos en la DDBB desde un datatable.
    /// </summary>
    /// <param name="dt">Datos a actualizar.</param>
    /// <param name="selectCommand">Comando SQL para generar los comandos INSERT,UPDATE,DELETE. Ej: Select * from </param>
    /// <param name="origen"></param>
    /// <returns></returns>
    /// <remarks></remarks>
    public static Exception EjecutarUpdate(ref DataTable dt, string selectCommand, clsVariables.e_TipoOrigen origen)
    {
        Exception ret = null; // New DataTable
        try
        {
            if (clsVariables.e_ProviderNombreAplicacion == clsVariables.eProviderNombre.MySqlClient)
            {
                return clsBBDD_MySQL.GestionDatos.EjecutarUpdate(dt, selectCommand, origen); //Tratamiento especial para MySQl pq. he tenido problemas para sobreescribir fechas
                //Return clsBBDD_MySQL.GestionDatos.DtObtenerConUpdate(selectCommandText, origen) 'NO puedo enviar selects complejas aquí
                //
            }
            else
            {
                ConnectionStringSettings c = clsVariables.e_Cc(origen);
                //Dim factory As DbProviderFactory = DbProviderFactories.GetFactory(c.ProviderName)
                DbDataAdapter adapter = FactoryBBDD.CreateDataAdapter();
                DbCommandBuilder builder = FactoryBBDD.CreateCommandBuilder();
                using (DbConnection cn = FactoryBBDD.CreateConnection())
                {
                    cn.ConnectionString = c.ConnectionString;
                    cn.Open();
                    using (DbCommand cm = FactoryBBDD.CreateCommand())
                    {
                        cm.Connection = cn;
                        cm.CommandType = CommandType.Text;
                        cm.CommandText = selectCommand;
                        adapter.SelectCommand = cm;
                        builder.DataAdapter = adapter;
                        adapter.Update(dt);
                    }

                }

            }
            //
        }
        catch (Exception ex)
        {
            ret = ex;
        }
        return ret;
    }
    //'
    /// <summary>
    /// Recuperar un dataTable desde un origen.
    /// </summary>
    /// <param name="selectCommandText"></param>
    /// <param name="origen"></param>
    /// <param name="bolObtenerSchema">Obtener info Extra como las primary keys</param>
    /// <returns></returns>
    /// <remarks></remarks>
    public static DataTable DtObtener(string selectCommandText, clsVariables.e_TipoOrigen origen, bool bolObtenerSchema = false)
    {
        DataTable ret;
        //'
        try
        {
            Console.WriteLine(selectCommandText);
            //
            if (clsVariables.e_ProviderNombreAplicacion == clsVariables.eProviderNombre.MySqlClient)
            {
                return clsBBDD_MySQL.GestionDatos.DtObtener(selectCommandText, origen, bolObtenerSchema); //Tratamiento especial para MySQl pq. he tenido problemas para sobreescribir fechas
                //Return clsBBDD_MySQL.GestionDatos.DtObtenerConUpdate(selectCommandText, origen) 'NO puedo enviar selects complejas aquí
                //
            }
            else
            {
                ret = new DataTable();
                ConnectionStringSettings c = clsVariables.e_Cc(origen);
                DataTable Dt2 = DtObtenerGetFactoryClasses();
                FactoryBBDD = DbProviderFactories.GetFactory(c.ProviderName);
                //
                using (DbConnection cn = FactoryBBDD.CreateConnection())
                {
                    cn.ConnectionString = c.ConnectionString;
                    cn.Open();
                    using (DbCommand cm = FactoryBBDD.CreateCommand())
                    {
                        cm.Connection = cn;
                        cm.CommandType = CommandType.Text;
                        cm.CommandText = selectCommandText; // "Select * FROM vis"
                        //Dim r As IDataReader = cm.ExecuteReader(CommandBehavior.CloseConnection)
                        // Create the DbDataAdapter.
                        DbDataAdapter adapter = FactoryBBDD.CreateDataAdapter();
                        adapter.SelectCommand = cm;
                        if (bolObtenerSchema)
                        {
                            //adapter.MissingSchemaAction = MissingSchemaAction.AddWithKey;
                            //adapter.MissingSchemaAction = MissingSchemaAction.Add;
                            //adapter.FillSchema(ret, SchemaType.Source); //No acaba de funcionar ok el MaxLengh
                        }
                        adapter.Fill(ret);
                    }

                }

            }
            //'
        }
        catch (Exception ex)
        { throw (ex); }//return null;}
        return ret;
    }

    #region EjecutarTransaccion    
    /// <summary>
    /// Ejecutar un conjunto de sqls. Si falla 1 hay rollback.
    /// Ej llamada: EjecutarTransaccion(cliente,  sSqls)
    /// </summary>
    /// <param name="origen"></param>
    /// <param name="dSqls"></param>
    /// <remarks></remarks>
    public static void EjecutarTransaccion(clsVariables.e_TipoOrigen origen, 
        string _strSql,
        bool _bolPegarSQlOnError)
    {
        System.Collections.Specialized.StringCollection dSqls = new System.Collections.Specialized.StringCollection();
        dSqls.Add(_strSql);
        EjecutarTransaccion(origen, dSqls, _bolPegarSQlOnError);
    }
    /// <summary>
    /// Ejecutar un conjunto de sqls. Si falla 1 hay rollback.
    /// Ej llamada: EjecutarTransaccion(cliente,  sSqls)
    /// </summary>
    /// <param name="origen"></param>
    /// <param name="dSqls"></param>
    /// <remarks></remarks>
    public static void EjecutarTransaccion(clsVariables.e_TipoOrigen origen,
                                            System.Collections.Specialized.StringCollection dSqls,
                                            bool _bolPegarSQlOnError)
    {
        ConnectionStringSettings c = clsVariables.e_Cc(origen);
        DbTransaction dbT;
        DbCommand dbC;
        //'
        FactoryBBDD = DbProviderFactories.GetFactory(c.ProviderName);
        using (DbConnection cn = FactoryBBDD.CreateConnection())
        {
            cn.ConnectionString = c.ConnectionString;

            cn.Open();

            dbC = cn.CreateCommand();

            dbT = cn.BeginTransaction();
            //
            dbC.Connection = cn;

            dbC.Transaction = dbT;
            //'
            try
            {
                foreach (string sqlActual in dSqls)
                {
                    dbC.CommandText = sqlActual;

                    dbC.ExecuteNonQuery();
                }
                //
                dbT.Commit(); // Intenta ejecutar la transacción

            }
            catch (Exception ex)
            {
                if (_bolPegarSQlOnError)
                {
                    if (MessageBox.Show(string.Format("Commit Exception Type: {0} {1}{1}Sql errónea: {2}{1}{1}Mensaje Error: {3}{1}{1}Desea pegar la sql en el portapapales de Windows?", ex.GetType(), Environment.NewLine, dbC.CommandText, ex.Message),
                                    "Error", MessageBoxButtons.YesNo, MessageBoxIcon.Error) == DialogResult.Yes)
                    {
                        (new Microsoft.VisualBasic.Devices.Computer()).Clipboard.SetText(dbC.CommandText);
                    }
                }
                //
                try
                {
                    dbT.Rollback(); // Intenta hacer el Rollback de la transacción.
                }
                catch (Exception ex2)
                {
                    throw new Exception(
                        string.Format("Rollback Exception Type: {0}{1}{1}Mensaje Error: {2}", ex2.GetType(), Environment.NewLine, ex2.Message),
                        ex2);

                }

                throw;
            }
        }

    }
    #endregion

    /// <summary>
    /// Pasas clave (key) y devuelve el valor transformado en lo q sea. De cliente y sistema
    /// </summary>
    /// <param name="strClave"></param>
    /// <remarks></remarks>
    public static object ObtenerVariables(string strClave, clsVariables.e_TipoOrigen TipoOrigen)
    {
        DataTable Dt;
        //'
        Dt = clsBBDD.DtObtener(String.Format(" SELECT * FROM variables{0}  WHERE clave = \'{1}\'",
            (TipoOrigen == clsVariables.e_TipoOrigen.Cliente ? "cliente" : "sistema"), strClave.Trim()), TipoOrigen, false);
        //
        if (Dt.Rows[0]["tipo"].ToString().ToLower() == "string")
        {
            return Dt.Rows[0]["cadena"];
        }
        else if (Dt.Rows[0]["tipo"].ToString().ToLower() == "integer")
        {
            return Dt.Rows[0]["numero"];
        }
        else if (Dt.Rows[0]["tipo"].ToString().ToLower() == "boolean")
        {
            return Dt.Rows[0]["booleano"];
        }
        else if (Dt.Rows[0]["tipo"].ToString().ToLower() == "double")
        {
            return Dt.Rows[0]["double"];
        }
        else if (Dt.Rows[0]["tipo"].ToString().ToLower() == "date")
        {
            return Dt.Rows[0]["fecha"];
        }
        else if (Dt.Rows[0]["tipo"].ToString().ToLower() == "datetime")
        {
            return Dt.Rows[0]["fechatiempo"];
        }
        else
        {
            Utiles.Errores.LanzarError(null, "VariablesObtener", "Tipo no programado" + Dt.Rows[0]["tipo"], null, MessageBoxIcon.Exclamation, true);
            return null;
        }
    }
    //'
    #region                                                                ObtenerString

    /// <summary>
    /// Ejecutar un commando SQL y devolver un valor de tipo string, del primer registro y el primer campo.
    /// </summary>
    /// <param name="strSql">Commando SQL a procesar</param>
    /// <param name="origen">CLiente o sistema</param>
    /// <param name="DefaultValue">El valor por defecto si no encuentra NADA.</param>
    /// <returns>String localizado o Valor por defecto indicado.</returns>
    /// <remarks></remarks>
    public static string ObtenerString(string strSql, clsVariables.e_TipoOrigen origen, string DefaultValue)
    {
        string sRet = DefaultValue;
        DataTable Dt;
        //'
        try
        {
            if (!strSql.Equals(string.Empty))
            {
                //-----
                //Inicializar
                Dt = DtObtener(strSql, origen, false);
                try
                {
                    sRet = Dt.Rows[0][0].ToString();
                }
                catch (Exception)
                {
                    //No habrán datos
                }
            }
        }
        catch (Exception ex)
        {
            throw (new Exception("Error al Ejecutar el Comando, AGeObtenerString", ex)); //  IsItCRMException.Process(ex, "Error al Ejecutar el Comando")
        }
        return sRet;
    }

    #endregion
    //
    #region                                                                ObtenerDateTimeSQl

    /// <summary>
    /// Ejecutar un commando SQL y devolver un valor de tipo date de sql. Lo transforma según provider
    /// </summary>
    /// <param name="strSql">Commando SQL a procesar</param>
    /// <param name="origen">CLiente o sistema</param>
    /// <param name="DefaultValue">El valor por defecto si no encuentra NADA. Variable como 'DateTime? _fechaBackup' para pasar null</param>
    /// <returns>date localizado o Valor por defecto indicado.</returns>
    /// <remarks></remarks>
    public static DateTime? ObtenerDateTimeSQl(string strSql, clsVariables.e_TipoOrigen origen, DateTime? DefaultValue)
    {
        DateTime? sRet = DefaultValue;
        DataTable Dt;
        //'
        try
        {
            if (!strSql.Equals(string.Empty))
            {
                //-----
                //Inicializar
                Dt = DtObtener(strSql, origen, false);
                try
                {
                    sRet = Convert.ToDateTime(Dt.Rows[0][0]);
                }
                catch (Exception)
                {
                    //No habrán datos
                }
            }
        }
        catch (Exception ex)
        {
            throw (new Exception("Error al Ejecutar el Comando, AGeObtenerString", ex)); //  IsItCRMException.Process(ex, "Error al Ejecutar el Comando")
        }
        return sRet;
    }

    #endregion
    //
    #region                                                                ObtenerBoolean
    /// <summary>
    /// Ejecutar un commando SQL y devolver un valor de tipo Boolean, del primer registro y el primer campo.
    /// </summary>
    /// <param name="strSql">Commando SQL a procesar</param>
    /// <param name="origen">CLiente o sistema</param>
    /// <param name="DefaultValue">El valor por defecto si no encuentra NADA.</param>
    /// <returns>Boolean localizado o Valor por defecto indicado.</returns>
    /// <remarks></remarks>
    public static Boolean ObtenerBoolean(string strSql, clsVariables.e_TipoOrigen origen, Boolean DefaultValue)
    {
        Boolean sRet = DefaultValue;
        DataTable Dt;
        //'
        try
        {
            if (!strSql.Equals(String.Empty))
            {
                Dt = DtObtener(strSql, origen, false);
                try
                { sRet = Convert.ToBoolean(Dt.Rows[0][0]); }
                catch (Exception)
                {
                    //No habrán datos
                }
            }
        }
        catch (Exception ex)
        {
            throw (new Exception("Error al Ejecutar el Comando, ObtenerBoolean", ex)); //  IsItCRMException.Process(ex, "Error al Ejecutar el Comando")
        }
        return sRet;
    }
    #endregion
    //'
    //
    /// <summary>
    /// Le pasas un date y te devuelve el date en el provider q toque
    /// </summary>
    /// <param name="strSql"></param>
    /// <param name="origen"></param>
    /// <returns></returns>
    public static object TransformDate(object datFechaObj, bool bolDevolucionTipoString = false)
    {
        switch (clsVariables.e_ProviderNombreAplicacion)
        {
            case clsVariables.eProviderNombre.Ninguno:
                return datFechaObj;
            case clsVariables.eProviderNombre.Odbc:
                return datFechaObj;
            case clsVariables.eProviderNombre.OleDb:
                return datFechaObj;
            case clsVariables.eProviderNombre.OracleClient:
                return datFechaObj;
            case clsVariables.eProviderNombre.SqlClient:
                return datFechaObj;
            case clsVariables.eProviderNombre.SqlServerCe:
                return datFechaObj;
            case clsVariables.eProviderNombre.SqlServerCe35:
                return datFechaObj;
            case clsVariables.eProviderNombre.OracleDataAccessClient:
                return datFechaObj;
            case clsVariables.eProviderNombre.MySqlClient:
                return clsBBDD_MySQL.cFecha(datFechaObj, bolDevolucionTipoString); //return datFecha;            
            default:
                return datFechaObj;
        }

    }

    //
    #region                                                                ObtenerDouble

    /// <summary>
    /// Ejecutar un commando SQL y devolver un valor de tipo Double, del primer registro y el primer campo.
    /// </summary>
    /// <param name="strSql">Commando SQL a procesar</param>
    /// <param name="origen">CLiente o sistema</param>
    /// <param name="DefaultValue">El valor por defecto si no encuentra NADA.</param>
    /// <returns>Double localizado o Valor por defecto indicado.</returns>
    /// <remarks></remarks>
    public static double ObtenerDouble(string strSql, clsVariables.e_TipoOrigen origen, double DefaultValue)
    {
        double sRet = DefaultValue;
        DataTable Dt;
        //'
        try
        {
            if (!strSql.Equals(string.Empty))
            {
                Dt = DtObtener(strSql, origen, false);
                try
                {
                    sRet = Convert.ToDouble(Dt.Rows[0][0]);
                }
                catch (Exception)
                {
                    //No habrán datos
                }
            }
        }
        catch (Exception ex)
        {
            throw (new Exception("Error al Ejecutar el Comando, AGeObtenerDouble", ex)); //  IsItCRMException.Process(ex, "Error al Ejecutar el Comando")
        }
        return sRet;
    }

    #endregion
    //'
    #endregion
    //'
    #region  Notas y pruebas
    #region                                                                Ejemeplo llamada procedure
    #region  sql Server
    //   USE [agiSEDSistema]
    //GO

    ///****** Object:  StoredProcedure [dbo].[agnSUPCola_Add]    Script Date: 11/30/2010 00:04:57 ******/
    //SET ANSI_NULLS ON
    //GO

    //SET QUOTED_IDENTIFIER ON
    //GO

    ///*
    //agnSUPCola_Add: Agregar un elemento a la cola, devolviendo un posible error.
    //	20100804 Integración SUP.
    //Devuelve @Ret:
    //   1000 Agregado
    //   1001 ProcesosCola Desactivado
    //   1002 ProcesosColaTipo Desactivado
    //(error) devuelve el @@ERROR
    //USO:
    //  GO
    //    Declare @Ret int
    //    EXEC agnSUPCola_Add @Ret=@Ret OUTPUT,@SUPTipoId=8001,@ClaveId='Por que yo lo valgo.',@Observaciones='soy el mejor'
    //    PRINT 'Resultado:' + CAST (@Ret AS varchar(50))
    //*/
    //	ALTER PROCEDURE [dbo].[agnSUPCola_Add](@ret int out, @SUPTipoId int, @ClaveId varchar(50), @Observaciones varchar(500))
    //	AS
    //	  IF EXISTS (SELECT TOP 1 TipoId FROM agnTCSistema WHERE TipoId = 'agnSUP' AND CodigoId='Disabled') -- Verificar si esta desactivado.
    //		SET @Ret = 1001  -- ProcesosCola Desactivado.
    //	  ELSE
    //		IF EXISTS(SELECT TOP 1 Id FROM agnSUPTipos WHERE Id=@SUPTipoID AND Inactivo=1) -- +Activo?.
    //          SET @Ret = 1002   -- ProcesosColaTipo Desactivado
    //		ELSE
    //		 BEGIN
    //		  INSERT INTO agnSUPCola (SUPTipoId,ClaveId,Observaciones) VALUES  (@SUPTipoId,@ClaveId,@Observaciones)
    //		  SET @ret = @@ERROR
    //		  IF @ret = 0 SET @Ret = 1000
    //		 END

    //GO

    #endregion
    //   ''' <summary>
    //   ''' Agregar un error a la cola de mensajes, llamar al procedure agnSUPColaUnique_Add (@ProcesoTipoId int, @ClaveId varchar(50), @Observaciones varchar(500)). Sin repetir ClaveId
    //   ''' </summary>
    //   ''' <param name="ProcesoTipoId"></param>
    //   ''' <param name="ClaveId"></param>
    //   ''' <param name="Observaciones"></param>
    //   ''' <param name="origen"></param>
    //   ''' <returns>retorna el parametro @Ret</returns>
    //   ''' <remarks></remarks>
    //   Public Shared Function SUPColaAddUnique(ByVal ProcesoTipoId As Integer, ByVal ClaveId As String, ByVal Observaciones As String, ByVal origen As e_TipoOrigen) As Integer ' ByVal selectCommandText As String, ByVal origen As e_TipoOrigen) As Integer
    //      Dim ret As Integer = -1
    //      Try
    //         Dim c As ConnectionStringSettings = e_Cc(origen)
    //         Dim factory As DbProviderFactory = DbProviderFactories.GetFactory(c.ProviderName)
    //         Using cn As DbConnection = FactoryBBDD.CreateConnection
    //            cn.ConnectionString = c.ConnectionString
    //            cn.Open()
    //            Using cm As DbCommand = FactoryBBDD.CreateCommand
    //               cm.Connection = cn
    //               With cm.Parameters 'param
    //                  Dim p As DbParameter = FactoryBBDD.CreateParameter()
    //                  p.ParameterName = "@Ret" 'Case sensitive NO
    //                  p.DbType = System.Data.DbType.Int32
    //                  p.Direction = ParameterDirection.InputOutput
    //                  p.Value = DBNull.Value ' IMPORTANTE !!!!!!!!
    //                  .Add(p)
    //                  p = FactoryBBDD.CreateParameter()
    //                  p.ParameterName = "@SUPTipoId"
    //                  p.DbType = System.Data.DbType.Int32
    //                  p.Value = ProcesoTipoId
    //                  .Add(p)
    //                  p = FactoryBBDD.CreateParameter()
    //                  p.ParameterName = "@ClaveId"
    //                  'p.DbType = DbType.String 'Default
    //                  p.Value = ClaveId
    //                  .Add(p)
    //                  p = FactoryBBDD.CreateParameter()
    //                  p.ParameterName = "@Observaciones"
    //                  p.Value = Observaciones
    //                  .Add(p)
    //               End With
    //               cm.CommandType = CommandType.StoredProcedure
    //               cm.CommandText = "agnSUPColaUnique_Add"
    //               Try
    //                  ret = cm.ExecuteNonQuery() 'cm.ExecuteNonQuery()
    //                  ret = cm.Parameters("@Ret").Value
    //               Catch ex As Exception
    //                  Throw ex
    //               End Try

    //            End Using
    //         End Using
    //      Catch ex As Exception
    //         Throw ex
    //      End Try
    //      Return ret
    //   End Function
    #endregion //Añadir mensaje.
    //'
    #region  No usado
    //'
    //Public Shared Function DtObtener2(ByVal selectCommandText As String, ByVal origen As e_TipoOrigen) As DataTable
    //   Dim Dt As DataTable
    //   Dim Da As DbDataAdapter
    //   Dim Cb As DbCommandBuilder
    //   ''
    //   Try
    //      Console.WriteLine(selectCommandText)
    //      Dim c As ConnectionStringSettings = e_Cc(origen)
    //      FactoryBBDD = DbProviderFactories.GetFactory(c.ProviderName)
    //      '
    //      Using cn As DbConnection = FactoryBBDD.CreateConnection
    //         '
    //         'Return Dt
    //         cn.ConnectionString = c.ConnectionString
    //         cn.Open()
    //         '
    //         'Create the DbCommand.
    //         Dim Co As DbCommand = FactoryBBDD.CreateCommand()
    //         Co.CommandText = selectCommandText
    //         Co.Connection = cn
    //         '
    //         ' Create the DbDataAdapter
    //         Da = FactoryBBDD.CreateDataAdapter
    //         Da.SelectCommand = Co
    //         '
    //         ''Fill
    //         'Dt = New DataTable
    //         'Da.Fill(Dt)
    //         '
    //         Cb = FactoryBBDD.CreateCommandBuilder
    //         With Cb
    //            .DataAdapter = Da
    //            .QuotePrefix = "" : .QuoteSuffix = ""
    //         End With
    //         Da.UpdateCommand = Cb.GetUpdateCommand
    //         Da.InsertCommand = Cb.GetInsertCommand
    //         Da.DeleteCommand = Cb.GetDeleteCommand
    //         Dt = New DataTable
    //         Da.Fill(Dt)
    //      End Using
    //      '
    //      Return Dt
    //   Catch ex As Exception
    //      Throw ex
    //   End Try
    //End Function
    // ''
    //Public Shared Function DtObtener20101223(ByVal selectCommandText As String, ByVal origen As e_TipoOrigen) As DataTable
    //   ' Create the DbProviderFactory and DbConnection.
    //   Try
    //      Dim c As ConnectionStringSettings = e_Cc(origen)
    //      Dim factory As DbProviderFactory = _
    //         DbProviderFactories.GetFactory(c.ProviderName)

    //      Dim connection As DbConnection = _
    //          factory.CreateConnection()
    //      connection.ConnectionString = c.ConnectionString
    //      Using connection

    //         ' Define the query.
    //         Dim queryString As String = _
    //           "SELECT * FROM Socios"

    //         'Create the DbCommand.
    //         Dim command As DbCommand = _
    //             factory.CreateCommand()
    //         command.CommandText = queryString
    //         command.Connection = connection

    //         ' Create the DbDataAdapter.
    //         Dim adapter As DbDataAdapter = _
    //             factory.CreateDataAdapter()
    //         adapter.SelectCommand = command

    //         ' Fill the DataTable
    //         Dim table As New DataTable
    //         adapter.Fill(table)

    //         'table.Rows(0).Item(13) = New Types.MySqlDateTime(Now)
    //         'table.Rows(0).Item(13) = Types.MySqlDateTime.GetMySqlDateTime(DateTime.Now)
    //         'Dim myDataReader As MySqlClient.MySqlDataReader
    //         'table.Rows(0).Item(13) = myDataReader.GetMySqlDateTime(DateTime.Now)
    //         'Display each row and column value.
    //         'Dim row As DataRow
    //         'Dim column As DataColumn
    //         'For Each row In table.Rows
    //         '   For Each column In table.Columns
    //         '      Console.WriteLine(row(column))
    //         '   Next
    //         'Next
    //         Return table
    //      End Using

    //   Catch ex As Exception
    //      Console.WriteLine(ex.Message)
    //   End Try

    //End Function

    //Public Shared Function DtObtener4(ByVal selectCommandText As String, ByVal origen As e_TipoOrigen) As DataTable
    //   'Dim Dt As DataTable
    //   ' ''
    //   'Try
    //   '   Dim c As ConnectionStringSettings = e_Cc(origen)
    //   '   Using cn2 As New MySqlClient.MySqlConnection(c.ConnectionString)
    //   '      Dim da2 As MySqlClient.MySqlDataAdapter = New MySqlClient.MySqlDataAdapter((selectCommandText, cn2)

    //   '      '      Dim cb As New SqlCommandBuilder(da2)
    //   '      Dim cb As New MySqlClient.MySqlCommandBuilder(da2)

    //   '      cb.QuotePrefix = "["
    //   '      cb.QuoteSuffix = "]"
    //   '      Dt = New DataTable
    //   '      da2.Fill(Dt)
    //   '   End Using

    //   '   Return Dt
    //   'Catch ex As Exception
    //   '   Throw ex
    //   'End Try
    //End Function
    // ''
    //Public Function ObtenerUpdate2(ByVal customers As DataTable, ByVal selectCommand As String) As Integer
    //   Using cn As DbConnection = DataFactoryHelper.CreateConnection(), _
    //      selectCommand As DbCommand = cn.CreateCommand(), _
    //      adapter As DbDataAdapter = DataFactoryHelper.CreateDataAdapter(), _
    //      builder As DbCommandBuilder = DataFactoryHelper.CreateCommandBuilder()

    //      selectCommand.CommandText = sSql
    //      adapter.SelectCommand = selectCommand
    //      builder.DataAdapter = adapter
    //      Return adapter.Update(customers)
    //   End Using
    //End Function
    //'
    //Public Function Obtener2(ByVal sSql As String) As DataTable
    //   Using cn As DbConnection = DataFactoryHelper.CreateConnection(), _
    //   selectCommand As DbCommand = cn.CreateCommand(), _
    //   adapter As DbDataAdapter = DataFactoryHelper.CreateDataAdapter()

    //      selectCommand.CommandText = sSql
    //      adapter.SelectCommand = selectCommand
    //      Dim customers As New DataTable
    //      adapter.Fill(customers)
    //      Return customers
    //   End Using
    //End Function
    //'
    //Public Shared Function ObtenerDataReader(ByVal selectCommandText As String, ByVal origen As e_TipoOrigen) As DbDataReader
    //   Dim ret As DbDataReader = Nothing
    //   If String.IsNullOrEmpty(selectCommandText) Then Throw New ArgumentNullException("ObtenerDataReader: selectCommandText")
    //   Try
    //      Dim c As ConnectionStringSettings = e_Cc(origen)
    //      Dim factory As DbProviderFactory = DbProviderFactories.GetFactory(c.ProviderName)
    //      Dim cn As DbConnection = FactoryBBDD.CreateConnection 'Using cn As DbConnection = FactoryBBDD.CreateConnection 'Using NO, ya que ret.IsClosed = True y FALLA al READ.
    //      cn.ConnectionString = c.ConnectionString
    //      cn.Open()
    //      Using cm As DbCommand = FactoryBBDD.CreateCommand
    //         cm.Connection = cn
    //         cm.CommandType = CommandType.Text
    //         cm.CommandText = selectCommandText
    //         ret = cm.ExecuteReader(CommandBehavior.CloseConnection)
    //      End Using
    //      'cn.Close()
    //      'End Using
    //   Catch ex As Exception
    //      Throw ex
    //   End Try
    //   Return ret
    //End Function
    //'
    //Public Class DataFactoryHelper
    //   Public Const DefaultConnectionStringName As String = "Cc"
    //   '
    //   Public Function GetProviderFactory(ByVal providerName As String) As DbProviderFactory
    //      Return DbProviderFactories.GetFactory(providerName)
    //   End Function
    //   '--------------
    //   Public Function CreateConnection(ByVal connectionStringName As String) As DbConnection
    //      Dim connectionStringSetting As ConnectionStringSettings = ConfigurationManager.ConnectionStrings(connectionStringName)
    //      Dim dbFactory As DbProviderFactory = GetProviderFactory(connectionStringSetting.ProviderName)
    //      Return dbFactoryBBDD.CreateConnection()
    //   End Function
    //   '
    //   Public Function CreateConnection() As DbConnection
    //      Return CreateConnection(DefaultConnectionStringName)
    //   End Function
    //   '--------------
    //   Public Function CreateDataAdapter(ByVal connectionStringName As String) As DbDataAdapter
    //      Dim connectionStringSetting As ConnectionStringSettings = ConfigurationManager.ConnectionStrings(connectionStringName)
    //      Dim dbFactory As DbProviderFactory = GetProviderFactory(connectionStringSetting.ProviderName)
    //      Return dbFactoryBBDD.CreateDataAdapter()
    //   End Function
    //   '
    //   Public Function CreateDataAdapter() As DbDataAdapter
    //      Return CreateDataAdapter(DefaultConnectionStringName)
    //   End Function
    //   '--------------
    //   Public Function CreateCommandBuilder(ByVal connectionStringName As String) As DbCommandBuilder
    //      Dim connectionStringSetting As ConnectionStringSettings = ConfigurationManager.ConnectionStrings(connectionStringName)
    //      Dim dbFactory As DbProviderFactory = GetProviderFactory(connectionStringSetting.ProviderName)
    //      Return dbFactoryBBDD.CreateCommandBuilder()
    //   End Function
    //   '
    //   Public Function CreateCommandBuilder() As DbCommandBuilder
    //      Return CreateCommandBuilder(DefaultConnectionStringName)
    //   End Function
    //End Class
    //'
    ///' <summary>
    ///' Recuperar una conexión a datos, desde el App.config. Buscamos Prefijo + ("ConexionSistema" o "ConexionCliente")
    ///' </summary>
    ///' <param name="Prefijo"></param>
    ///' <param name="tipo"></param>
    ///' <returns></returns>
    ///' <remarks></remarks>
    //Public Shared Function ObtenerConnectionStrings(ByVal Prefijo As String, ByVal tipo As eProviderNombre) As System.Configuration.ConnectionStringSettings  ' ByVal Key As String, Optional ByVal DefaultValue As String = "") As String
    //   Dim ret As ConnectionStringSettings = Nothing 'String = DefaultValue                   'Valor a retornar, xDefecto (DefaultValue)
    //   Try
    //      ret = ConfigurationManager.ConnectionStrings(Prefijo & "Conexion" & tipo.ToString("F")) '.ToString       'Buscar Prefijo + Key
    //      If (ret Is Nothing) AndAlso (Not String.IsNullOrEmpty(Prefijo)) Then ret = System.Configuration.ConfigurationManager.ConnectionStrings("Conexion" & tipo.ToString("F"))
    //   Catch ex As Exception
    //      'Si no existe, no lanza error, simplemente ret = Nothing
    //      ''-----
    //      ''No Existe la Clave (Si se había indicado Prefijo, buscar sin prefijo, sino DefaultValue)
    //      'If Not Prefijo.Equals(String.Empty) Then
    //      '   Try
    //      '      ret = System.Configuration.ConfigurationManager.ConnectionStrings("Conexion" & tipo.ToString("F"))
    //      '   Catch ex2 As Exception
    //      '   End Try
    //      'End If
    //   End Try
    //   Return ret                                         'Retornar Valor
    //End Function
    #endregion
    #endregion
    //'
}


